import 'dart:async';
import 'dart:typed_data';

import 'package:flutter/material.dart';
import 'dart:ui' as ui;

class ClipImgPage extends StatefulWidget {
  const ClipImgPage({super.key});

  @override
  State<ClipImgPage> createState() => _ClipImgPageState();
}

class _ClipImgPageState extends State<ClipImgPage> {
  final String imageUrl =
      'https://admin.rutang.cn/prod-api/profile/tmp/upload/wx_XKQQlTG4_6e16c362349e4a76b57c4ffd9c216c35.jpeg';
  ImageProvider? originalImage;
  Uint8List? clippedImageBytes;
  bool isClipped = false;
  bool isLoading = false;

  @override
  void initState() {
    super.initState();
    originalImage = NetworkImage(imageUrl);
  }

  Future<void> clipImage() async {
    setState(() {
      isLoading = true;
    });

    try {
      // 创建一个ImageStream来加载图片
      final ImageStream stream = originalImage!.resolve(
        const ImageConfiguration(),
      );
      final Completer<ui.Image> completer = Completer<ui.Image>();

      late final ImageStreamListener listener;
      listener = ImageStreamListener(
        (ImageInfo info, bool _) {
          completer.complete(info.image);
          stream.removeListener(listener);
        },
        onError: (dynamic error, StackTrace? stackTrace) {
          completer.completeError(error, stackTrace);
          stream.removeListener(listener);
        },
      );
      stream.addListener(listener);

      // 等待图片加载完成
      final ui.Image image = await completer.future;

      // 计算裁剪区域（中间部分）
      final int width = image.width;
      final int height = image.height;
      final int centerX = width ~/ 2;
      final int centerY = height ~/ 2;

      // 裁剪区域大小（这里取图片宽高的一半作为裁剪区域）
      final int cropWidth = width ~/ 2;
      final int cropHeight = height ~/ 2;

      // 计算裁剪区域的左上角坐标
      final int left = centerX - cropWidth ~/ 2;
      final int top = centerY - cropHeight ~/ 2;
    
      // print('${left},${top},${width},${height},${cropWidth},${cropHeight}');
      
      // 创建一个新的图片，用于绘制裁剪后的图片
      final ui.PictureRecorder recorder = ui.PictureRecorder();
      final Canvas canvas = Canvas(recorder);
      final Paint paint = Paint();

      // 使用drawImageRect进行真实裁剪 使用 canvas.drawImageRect 方法进行实际的图片裁剪，该方法从源图像的指定区域(src)裁剪内容并绘制到目标区域(dst)
      canvas.drawImageRect(
        image,
        Rect.fromLTWH(
          left.toDouble(),
          top.toDouble(),
          cropWidth.toDouble(),
          cropHeight.toDouble(),
        ),
        Rect.fromLTWH(0, 0, cropWidth.toDouble(), cropHeight.toDouble()),
        paint,
      );

      // 将绘制的内容转换为图片
      final ui.Picture picture = recorder.endRecording();
      final ui.Image croppedImage = await picture.toImage(
        cropWidth,
        cropHeight,
      );

      // 将图片转换为字节数据
      final ByteData? byteData = await croppedImage.toByteData(
        format: ui.ImageByteFormat.png,
      );
      final Uint8List pngBytes = byteData!.buffer.asUint8List();

      setState(() {
        clippedImageBytes = pngBytes;
        isClipped = true;
        isLoading = false;
      });
    } catch (e) {
      print('裁剪图片时出错: $e');
      setState(() {
        isLoading = false;
      });
    }
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: const Text("Clip Image Page")),
      body: Center(
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: [
            // 显示原始图片或裁剪后的图片
            if (!isClipped)
              Image.network(imageUrl)
            else
              Column(
                children: [
                  const Text(
                    '原图：',
                    style: TextStyle(fontSize: 16, fontWeight: FontWeight.bold),
                  ),
                  SizedBox(height: 10),
                  Image.network(imageUrl, height: 150),
                  SizedBox(height: 20),
                  const Text(
                    '裁剪后（中间部分）：',
                    style: TextStyle(fontSize: 16, fontWeight: FontWeight.bold),
                  ),
                  SizedBox(height: 10),
                  clippedImageBytes != null
                      ? Image.memory(
                          clippedImageBytes!,
                        ) // 从内存中的二进制数据（通常是字节数据）创建图像的一个构造函数
                      : Text('裁剪失败'),
                ],
              ),
            SizedBox(height: 20),
            if (isLoading)
              CircularProgressIndicator()
            else
              ElevatedButton(
                onPressed: () {
                  clipImage();
                },
                child: Text('裁剪'),
              ),
          ],
        ),
      ),
    );
  }
}
